using System;

namespace System.Resources.SqlResource
{
    /// <summary>
    /// Stores all the resources localized for one particular culture, 
    /// ignoring all other cultures, including any fallback rules.
    /// </summary>
    public class SqlResourceSet : ResourceSet
    {
        private readonly Globalization.CultureInfo _ci = null;
        private const string SQLRESOURCESET = "SqlResourceSet_";

        /// <summary>
        /// Creates a new instance of the ResourceSet class using the system default SqlResourceReader that reads resources from the given stream.
        /// </summary>
        /// <param name="ci">The Culture Info of resources to be read. If Culture Info not exist, stored pricedure return default Culture Info.</param>
        public SqlResourceSet(Globalization.CultureInfo ci)
        {
            CSUtil u = new CSUtil();
            ISqlResourceGetData s = u.CreateInstance();

            _ci = ci;
            Table = (Collections.Hashtable)System.Web.HttpContext.Current.Application[SQLRESOURCESET + _ci.Name];

            //Verify status of table.
            if ((Table == null) || (s.RebuildResourceSet != (string)Table["Rebuild_ResourceSet"]))
            {
                InserDataInApplicationCache(ci);
            }
            else
            {
                System.Diagnostics.Trace.WriteLine(SQLRESOURCESET + _ci.Name + " -> Get data from ApplicationCache.");
                //base.Table = (System.Collections.Hashtable)System.Web.HttpContext.Current.Application[SQLRESOURCESET + _ci.Name];
            }           
        }

        /// <summary>
        /// Load in Application hashtable with all resource for this Culture Info.
        /// </summary>
        /// <param name="ci">The Culture Info of resources to be read.</param>
        private void InserDataInApplicationCache(Globalization.CultureInfo ci)
        {
            CSUtil u = new CSUtil();
            ISqlResourceGetData s = u.CreateInstance(); 
            
            System.Diagnostics.Trace.WriteLine("InserDataInApplicationCache -> Inser data in ApplicationCache.");

            Reader = new SqlResourceReader(ci);
            Table = null;
            Table = new Collections.Hashtable();
            ReadResources();

            //Add guid to hashtable for identify if necessary refresh.
            Table.Add("Rebuild_ResourceSet", s.RebuildResourceSet);
            
            System.Web.HttpContext.Current.Application.Remove(SQLRESOURCESET + _ci.Name);
            System.Web.HttpContext.Current.Application.Add(SQLRESOURCESET + _ci.Name, base.Table);
        }

        protected override void ReadResources()
        {
            base.ReadResources();
        }
        public override void Close()
        {
            base.Close();
        }

        public override Type GetDefaultReader()
        {
            return typeof(SqlResourceReader);
        }
        public override Type GetDefaultWriter()
        {
            return typeof(SqlResourceWriter);
        }

        /// <summary>
        /// Searches for a String resource with the specified name.
        /// </summary>
        /// <param name="name">Case-sensitive name of the resource to search for. </param>
        /// <returns>The requested resource.</returns>
        public override string GetString(string name)
        {
            return ((CSResource)base.GetObject(name)).ParamStringValue;
        }

        /// <summary>
        /// Searches for a resource object with the specified name.
        /// </summary>
        /// <param name="name">Case-sensitive name of the resource to search for. </param>
        /// <returns>The requested resource.</returns>
        public override object GetObject(string name)
        {
            object o1 = ((CSResource)base.GetObject(name)).ParamObjectValue;
            //object o2 = ObjectByteArrayConverter.ByteArrayToObject((byte[])o1);
            return o1;
        }

        /// <summary>
        /// Searches for a String resource with the specified name in a case-insensitive manner, if requested.
        /// </summary>
        /// <param name="name">Name of the resource to search for. </param>
        /// <param name="ignoreCase">Indicates whether the case of the case of the specified name should be ignored. </param>
        /// <returns>The requested resource.</returns>
        public override string GetString(string name, bool ignoreCase)
        {
            return ((CSResource)base.GetObject(name, ignoreCase)).ParamStringValue;
        }

        /// <summary>
        /// Searches for a resource object with the specified name in a case-insensitive manner, if requested.
        /// 
        /// </summary>
        /// <param name="name">Name of the resource to search for. </param>
        /// <param name="ignoreCase">Indicates whether the case of the specified name should be ignored. </param>
        /// <returns>The requested resource.</returns>
        public override object GetObject(string name, bool ignoreCase)
        {
            object o1 = ((CSResource)base.GetObject(name, ignoreCase)).ParamObjectValue;
            //object o2 = ObjectByteArrayConverter.ByteArrayToObject((byte[])o1);
            return o1;
        }
    }
}
